<template>
    <div class="chart-wrapper">
        <div ref="chartEl" class="chart-container"></div>
    </div>
</template>

<script setup>
import { ref, onMounted, onBeforeUnmount, watch } from 'vue'
import { useECharts } from '@/utils/echarts/useECharts'
import echarts from '@/plugins/echarts'
import dayjs from '@/plugins/dayjs'
import FileSaver from 'file-saver'

// 定义组件属性
const props = defineProps({
    // 图表数据
    chartData: {
        type: Object,
        required: true,
        default: () => ({
            items: [],
            time_start: 0,
            time_end: 0,
            switch_name: '',
            port_name: '',
            reference_95th: 0
        })
    },
    // 图表标题
    title: {
        type: String,
        default: ''
    },
    // 图表副标题
    subTitle: {
        type: String,
        default: ''
    },
    // 图表高度
    height: {
        type: String,
        default: '300px'
    },
    // 渲染器类型：'canvas' 或 'svg'
    renderer: {
        type: String,
        default: 'canvas'
    },
    // 主题
    theme: {
        type: String,
        default: 'light'
    },
    // 入口流量系列名称
    inSeriesName: {
        type: String,
        default: '入口流量'
    },
    // 出口流量系列名称
    outSeriesName: {
        type: String,
        default: '出口流量'
    },
    // 入口流量颜色
    inColor: {
        type: String,
        default: '#20c83b'
    },
    // 出口流量颜色
    outColor: {
        type: String,
        default: '#2781de'
    },
    // 95th百分位线颜色
    p95LineColor: {
        type: String,
        default: '#d00'
    },
    // 时间格式
    timeFormat: {
        type: String,
        default: 'MM-DD HH:mm:ss'
    },
    // 单位基数
    baseUnit: {
        type: Number,
        default: 1000
    },
    // 底部文字大小
    bottomTextSize: {
        type: Number,
        default: 10
    },
    // 标题文字大小
    titleTextSize: {
        type: Number,
        default: 14
    },
})

// 事件
const emit = defineEmits(['chartReady', 'chartClick', 'chartDataZoom'])

// 响应式引用
const chartEl = ref(null)
let chartInstance = null

// 主入口
const renderChart = (config) => {
    if (!chartEl.value) return

    if (chartInstance) {
        chartInstance.dispose()
    }

    chartInstance = echarts.init(chartEl.value, props.theme, { renderer: props.renderer })
    chartInstance.setOption(config)

    // 绑定事件
    chartInstance.on('click', (params) => {
        emit('chartClick', params)
    })

    chartInstance.on('datazoom', (params) => {
        emit('chartDataZoom', params)
    })

    // 通知图表已准备好
    emit('chartReady', chartInstance)
}

// 核心逻辑
const initChart = () => {
    if (!chartEl.value) return
    const rawData = props.chartData
    const processed = processData(rawData)
    renderChart(buildChartConfig(processed))
    setupResizeListener()
}

const processData = (rawData) => {
    const items = rawData.items || []
    const stats = {
        in: { values: [], max: 0, avg: 0, p95: 0 },
        out: { values: [], max: 0, avg: 0, p95: 0 }
    }

    // 数据转换和基础统计
    const timeline = items.map((item) => {
        const inValue = convertToBps(item.in_rates)
        const outValue = convertToBps(item.out_rates)

        stats.in.values.push(inValue)
        stats.out.values.push(outValue)
        stats.in.max = Math.max(stats.in.max, inValue)
        stats.out.max = Math.max(stats.out.max, outValue)

        return formatTime(item.timeline_5min)
    })

    // 高级统计计算
    stats.in.avg = calculateAverage(stats.in.values)
    stats.out.avg = calculateAverage(stats.out.values)
    stats.in.p95 = calculatePercentile(stats.in.values, 95)
    stats.out.p95 = calculatePercentile(stats.out.values, 95)

    return {
        timeline,
        series: {
            in: stats.in.values,
            out: stats.out.values
        },
        stats,
        meta: {
            title: props.title + ` 流量图` || `${rawData.switch_name} ${rawData.port_name}  ` + `流量图`,
            timeRange: `${formatTime(rawData.time_start)} - ${formatTime(rawData.time_end)}`
        }
    }
}

const buildChartConfig = (data) => {
    return {
        title: {
            text: data.meta.title,
            subtext: props.subTitle || data.meta.timeRange,
            left: 'center',
            textStyle: {
                fontFamily: 'Consolas,Monaco,monospace',
                fontSize: props.titleTextSize,
            }
            
        },
        legend: [
            {
                data: [props.inSeriesName, props.outSeriesName],
                orient: 'vertical',
                icon: 'rect',
                textStyle: {
                    fontFamily: 'Consolas,Monaco,monospace',
                    fontSize: props.bottomTextSize,
                },
                formatter: (name) => {
                    const stats = name === props.inSeriesName ? data.stats.in : data.stats.out
                    return `${name} | 最大:${formatValue(stats.max)}    平均:${formatValue(stats.avg)}    95th:${formatValue95(stats.p95)}`
                },
                left: '10%',
                bottom: 50,
                itemGap: 7
            },
            {
                data: [
                    {
                        name: props.inSeriesName
                    }
                ],
                itemStyle: {
                    color: '#e56d6d'
                },
                icon: 'diamond',
                orient: 'vertical',
                textStyle: {
                    fontFamily: 'Consolas,Monaco,monospace',
                    fontSize: props.bottomTextSize,
                },
                formatter: (name) => {
                    const stats = name === props.inSeriesName ? data.stats.in : data.stats.out
                    // 这里出口流量的95th和入口流量的95th取最大值
                    const max95th = Math.max(data.stats.in.p95, data.stats.out.p95);
                    return `${props.inSeriesName} + ${props.outSeriesName} 95th: ${formatValue95(max95th)} bps`
                },
                left: '10%',
                bottom: 30,
                itemGap: 7
            }
        ],
        xAxis: {
            type: 'category',
            data: data.timeline,
            axisLine: {
                lineStyle: {
                    width: 1
                }
            }
        },
        yAxis: {
            type: 'value',
            axisLabel: { formatter: formatValue }
        },
        series: [
            createSeriesin(props.inSeriesName, data.series.in, props.inColor, data.stats.in.p95, 1),
            createSeriesout(props.outSeriesName, data.series.out, props.outColor, data.stats.out.p95, 0)
        ],
        toolbox: {
            feature: {
                myTools1: {
                    show: !0,
                    title: "下载CSV文件",
                    icon: "path://M4.7,22.9L29.3,45.5L54.7,23.4M4.6,43.6L4.6,58L53.8,58L53.8,43.6M29.2,45.1L29.2,0",
                    onclick: function () {
                        // 获取图表数据
                        const chartData = props.chartData;
                        const processed = processData(chartData);

                        // 构建CSV内容
                        let csvContent = "Title:," + processed.meta.title + "\n";
                        csvContent += "Vertical Label:,bit per second\n";
                        csvContent += "Start Date:," + formatTime(chartData.time_start) + "\n";
                        csvContent += "End Date:," + formatTime(chartData.time_end) + "\n";
                        csvContent += "Step:,300\n";
                        csvContent += "Total Rows:," + chartData.items.length + "\n";
                        csvContent += "95th Percentile:,In:," + processed.stats.in.p95 + ",Out:," + processed.stats.out.p95 + "\n";
                        csvContent += "Date,Inbound,Outbound\n";

                        // 添加数据行
                        chartData.items.forEach(item => {
                            csvContent += formatTime(item.timeline_5min) + "," +
                                (item.in_rates * 8) + "," +
                                (item.out_rates * 8) + "\n";
                        });

                        // 创建Blob对象
                        const blob = new Blob([csvContent], {
                            type: "text/csv;charset=utf-8"
                        });

                        // 生成文件名（包含时间戳）
                        const timestamp = parseInt(new Date().getTime() / 1000);
                        const filename = chartData.switch_name + "_" + processed.meta.title + "_" + timestamp + ".csv";

                        // 保存文件
                        FileSaver.saveAs(blob, filename);
                    }
                }
            },
            top: "80%",
            right: "3%"
        },
        tooltip: {
            trigger: 'axis',
            axisPointer: {
                type: 'cross'
            },
            formatter: (params) => {
                let content = `<b>${params[0].axisValue}</b>`
                params.forEach((p) => {
                    content += `<br/>${p.marker} ${p.seriesName}: ${formatValue(p.value)}`
                })
                return content
            }
        },
        grid: { bottom: 120 }
    }
}

// 创建系列配置（包含95th标记）入口流量
const createSeriesin = (name, data, color, p95Value, isshow) => {
    return {
        name,
        type: 'line',
        data,
        symbol: 'none',
        lineStyle: { color, width: 1 },
        itemStyle: {
            color: color
        },
        areaStyle: {
                color: new echarts.graphic.LinearGradient(0, 0, 0, 1, [
                    { offset: 0, color: `${color}` },
                    { offset: 1, color: `${color}` }
                ])
            },
        markLine: {
        silent: true,
            lineStyle: { color: props.p95LineColor, type: 'solid', width: 1 },
        data: [{ yAxis: p95Value }],
            label: {
            show: true,
                position: 'end',
                    formatter: `${name}\n\n95th: ${formatValue(p95Value)}`,
                        color: props.p95LineColor,
                            backgroundColor: 'rgba(255,255,255,0.8)',
                                padding: [4, 8],
                                    borderRadius: 4,
                                        distance: 10
        }
    }
}
}
// 创建系列配置（包含95th标记）出口流量
// 创建系列配置（包含95th标记）
const createSeriesout = (name, data, color, p95Value, isshow) => {
    return {
        name,
        type: 'line',
        data,
        symbol: 'none',
        lineStyle: { color, width: 2 },
        itemStyle: {
            color: color
        },
      
        markLine: {
        silent: true,
            lineStyle: { color: props.p95LineColor, type: 'solid', width: 1 },
        data: [{ yAxis: p95Value }],
            label: {
            show: true,
                position: 'end',
                    formatter: `${name}\n\n95th: ${formatValue(p95Value)}`,
                        color: props.p95LineColor,
                            backgroundColor: 'rgba(255,255,255,0.8)',
                                padding: [4, 8],
                                    borderRadius: 4,
                                        distance: 10
        }
    }
}
}
// 工具方法
const formatValue = (value) => {
    const units = ['', 'K', 'M', 'G']
    let unitIndex = 0
    let formattedValue = value

    while (formattedValue >= props.baseUnit && unitIndex < units.length - 1) {
        formattedValue /= props.baseUnit
        unitIndex++
    }

    return `${formattedValue.toFixed(2)} ${units[unitIndex]}bps`
}
// 工具方法
const formatValue95 = (value) => {
    const units = ['', 'K', 'M']
    let unitIndex = 0
    let formattedValue = value

    while (formattedValue >= props.baseUnit && unitIndex < units.length - 1) {
        formattedValue /= props.baseUnit
        unitIndex++
    }

    return `${formattedValue.toFixed(2)} ${units[unitIndex]}bps`
}
const formatTime = (timestamp) => {
    return dayjs(timestamp * 1000)
        .format(props.timeFormat)
}

const convertToBps = (byteValue) => {
    return byteValue * 8 // 字节转比特
}

const calculateAverage = (values) => {
    if (!values.length) return 0
    return values.reduce((sum, v) => sum + v, 0) / values.length
}

const calculatePercentile = (values, percentile) => {
    if (!values.length) return 0
    const sorted = [...values].sort((a, b) => a - b)
    const index = Math.ceil((sorted.length * percentile) / 100) - 1
    return sorted[index] || 0
}

// 响应式处理
const setupResizeListener = () => {
    if (!chartEl.value) return

    const observer = new ResizeObserver(() => {
        if (chartInstance) {
            chartInstance.resize()
        }
    })

    observer.observe(chartEl.value)

    // 返回清理函数
    return () => {
        if (chartEl.value) {
            observer.unobserve(chartEl.value)
        }
    }
}

// 监听属性变化
watch(
    () => props.chartData,
    () => {
        initChart()
    },
    { deep: true }
)

// 生命周期
onMounted(() => {
    initChart()
})

onBeforeUnmount(() => {
    if (chartInstance) {
        chartInstance.dispose()
        chartInstance = null
    }
})

// 暴露方法
defineExpose({
    getChartInstance: () => chartInstance,
    refresh: initChart,
    resize: () => {
        if (chartInstance) {
            chartInstance.resize()
        }
    }
})
</script>

<style scoped>
.chart-wrapper {
    width: 100%;
    height: v-bind(height);
}

.chart-container {
    width: 100%;
    height: 100%;
}
</style>